/*
 * Copyright (C) 2024 Huawei Device Co., Ltd.
 * Licensed under the Apache License, Version 2.0 (the 'License');
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an 'AS IS' BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

#ifndef LOTTIEPRO_LOTTIELISTENER_H
#define LOTTIEPRO_LOTTIELISTENER_H

#include "common/napi_helper.h"
#include "napi/native_api.h"
#include <functional>

namespace LottiePro {

enum class LottieEventType {
    ON_DRAW_FRAME,
    ON_ENTER_FRAME,
    ON_LOOP_COMPLETE,
    ON_COMPLETE,
    ON_SEGMENT_START,
    ON_DESTROY,
    ON_CONFIG_READY,
    ON_DATA_READY,
    ON_DOM_LOADED,
    ON_ERROR,
    ON_DATA_FAILED,
    ON_LOADED_IMAGES
};

class LottieListener {
public:
    explicit LottieListener(napi_env env);
    ~LottieListener();

    /**
     * @brief 注册LottieListener对象所有存在的事件回调
     * @param listenerJsObject JS侧的LottieListener对象
     */
    void InitListenerCallback(napi_value listenerJsObject);

    /**
     * @brief 注册制定的事件回调
     * @param callbackFunc 回调函数
     * @param eventType 需要注册回调的事件类型
     */
    void RegisterCallback(napi_value callbackFunc, LottieEventType eventType);

    /**
     * @brief 取消注册指定的事件回调
     * @param eventName LottieEventType
     */
    void UnRegisterCallback(LottieEventType eventType);

    /**
     * @brief 触发事件回调
     * @param eventName
     */
    void TriggerEvent(LottieEventType eventType);

private:
    /**
     * @brief 注册LottieListener自身的某个事件回调
     * @param listenerJsObject JS侧的LottieListener对象
     * @param eventType 需要注册回调的事件类型
     */
    void RegisterSelfCallback(napi_value listenerJsObject, LottieEventType eventType);

    /**
     * @brief 删除回调引用
     * @param callbackRef napi_ref
     */
    void DeleteCallbackReference(napi_ref &callbackRef);

    NapiHelper napiHelper_;
    napi_ref jsThisRef_;
    std::unordered_map<LottieEventType, std::function<void()>> funcMap_; // 事件与回调函数的映射
    std::unordered_map<LottieEventType, napi_ref> callbackRefs_;         // 事件与回调引用的映射
};

} // namespace LottiePro
#endif // LOTTIEPRO_LOTTIELISTENER_H
